﻿
using Furion;
using Furion.DatabaseAccessor;
using Furion.DataEncryption;
using Furion.FriendlyException;
using Furion.UnifyResult;
using Mapster;
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Authentication.Cookies;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Pear.Application.UserCenter;
using Pear.Core;
using Pear.Web.Core;
using System;
using System.Collections.Generic;
using System.Security.Claims;
using System.Threading.Tasks;

namespace Pear.Web.Entry.Controllers
{
    [AllowAnonymous]
    public class UserController : Controller
    {
        /// <summary>
        /// 用户仓储
        /// </summary>
        private readonly IRepository<User> _userRepository;
        private readonly string CaptchaAESEncryptionKey = "zzzzzzzzzzzzzzzzzzzz123456789012";

        /// <summary>
        /// 用户管理类
        /// </summary>
        private readonly IUserManager _userManager;

        public UserController(IRepository<User> userRepository
            , IUserManager userManager)
        {
            _userRepository = userRepository;
            _userManager = userManager;
        }

        /// <summary>
        /// 用户登录
        /// </summary>
        /// <param name="model"></param>
        /// <param name="returnUrl"></param>
        /// <returns></returns>
        [HttpPost]
        public async Task<IActionResult> Login([FromBody] MvcLoginInput input)
        {
            if(input.Captcha != AESEncryption.Decrypt(App.GetService<CookieUtil>().Get("captcha"), CaptchaAESEncryptionKey))
            {
                return Json(new RESTfulResult<object>
                {
                    StatusCode = 200,
                    Succeeded = false,
                    Errors = Oops.Oh(SystemErrorCodes.u1012),
                    Extras = UnifyContext.Take(),
                    Timestamp = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds()
                });
            }

            // 获取加密后的密码
            var encryptPassword = MD5Encryption.Encrypt(input.Password.Trim());

            // 判断用户名或密码是否正确
            var user = await _userRepository.FirstOrDefaultAsync(u => u.Account.Equals(input.Account) && u.Password.Equals(encryptPassword));

            if (!(user != null && user.Id > 0))
            {
                return Json(new RESTfulResult<object>
                {
                    StatusCode = 200,
                    Succeeded = false,
                    Errors = Oops.Oh(SystemErrorCodes.u1000),
                    Extras = UnifyContext.Take(),
                    Timestamp = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds()
                });
            }

            // 更新登录时间
            user.SigninedTime = DateTimeOffset.Now;

            // 映射结果
            var output = user.Adapt<LoginOutput>();

            // 生成 token
            var accessToken = output.AccessToken = JWTEncryption.Encrypt(new Dictionary<string, object>
            {
                { "UserId",user.Id },
                { "Account",user.Account }
            });

            //创建用户身份标识
            var claimsIdentity = new ClaimsIdentity(CookieAuthenticationDefaults.AuthenticationScheme);
            claimsIdentity.AddClaims(new List<Claim>()
                    {
                        new Claim("UserId", output.Id.ToString()),
                        new Claim("Account", output.Account),
                        new Claim(ClaimTypes.Name, output.Account),

                    });

            await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, new ClaimsPrincipal(claimsIdentity));


            return Json(new RESTfulResult<object>
            {
                StatusCode = 200,
                Succeeded = true,
                Data = output,
                Extras = UnifyContext.Take(),
                Timestamp = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds()
            });
        }


        /// <summary>
        /// 获取验证码
        /// </summary>
        /// <returns></returns>
        public IActionResult CaptchaImage()
        {
            Tuple<string, int> captchaCode = CaptchaUtil.GetCaptchaCode();
            byte[] bytes = CaptchaUtil.CreateCaptchaImage(captchaCode.Item1);
            App.GetService<CookieUtil>().Set("captcha", AESEncryption.Encrypt(captchaCode.Item2.ToString(),CaptchaAESEncryptionKey));
            return  File(bytes, @"image/jpeg");
        }


        /// <summary>
        /// 登出系统
        /// </summary>
        [AppAuthorize]
        
        public new async Task<RedirectToActionResult> SignOut()
        {
            await HttpContext.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);
             
            return RedirectToAction("Login");
        }


        /// <summary>
        /// 用户登录页面
        /// </summary>
        /// <returns></returns>
        public IActionResult Login()
        {
            return View();
        }

        /// <summary>
        /// 用户注册
        /// </summary>
        /// <returns></returns>
        public IActionResult Register()
        {
            return View();
        }



        /// <summary>
        /// 用户没有权限
        /// </summary>
        /// <returns></returns>
        public IActionResult AccessDenied()
        {
            return View();
        }

    }
}